//-----------------------------基础版promise
/* 
下面是实现基础的promise功能，一个函数调用表达式只能进行一次then的调用，无法多次进行then的链式调用。
 */
//宏变量
const PENDING = 'PENDING';
const RESOLVE = 'RESOLVE';
const REJECT = 'REJECT';

class Promise {
    //1、看这个属性能否在原型上使用
    //2、看属性是否公用
    constructor(executor){
        this.status = PENDING;//初始状态默认是pending状态
        this.value = undefined;//成功的值
        this.reason = undefined;//失败的原因
        this.onfulfilledCallbacks = [];
        this.onrejectedCallbacks = [];

        //成功函数
        let resolve = (value) => {
            if(this.status === PENDING){
                this.status = RESOLVE;
                this.value = value;
                this.onfulfilledCallbacks.forEach(fn => fn());
            }
        }

        //失败函数
        let reject = (reason) => {
            if(this.status === PENDING){
                this.status = REJECT;
                this.reason = reason;
                this.onrejectedCallbacks.forEach(fn => fn());
            }
        }

        try {
            executor(resolve,reject);//实例化的时候，默认执行器会立即执行
        }catch(e){
            reject(e);//如果执行时发生错误，等价于调用了失败方法
        }
    }
    then(onfulfilled,onrejected){//then目前有两个参数，后面的升级版promise会把参数改为不定的。
        //同步处理
        if(this.status === RESOLVE){
            onfulfilled(this.value);
        }

        //同步处理
        if(this.status === REJECT){
            onrejected(this.reason);
        }

        //为解决异步（用到了发布订阅思想），例如实例化promise时执行器中用了setTimeout延迟3s后再调用resolve。
        if(this.status === PENDING){
            //如果是异步，就先订阅
            this.onfulfilledCallbacks.push(() => {
                //这里还能自定义做点啥，有可扩展性
                onfulfilled(this.value);
            });

            this.onrejectedCallbacks.push(() => {
                //这里还能自定义做点啥，有可扩展性
                onrejected(this.reason);
            });
        }
    }
    
}

module.exports = Promise;